function processFile(blob, fileName) { var libs = []; if (typeof marked === 'undefined') { libs.push(loadScriptPromise('https://cdnjs.cloudflare.com/ajax/libs/marked/12.0.1/marked.min.js')); } if ((typeof window.jspdf === 'undefined' || typeof window.jspdf.jsPDF === 'undefined') && typeof jsPDF === 'undefined') { libs.push(loadScriptPromise('https://cdnjs.cloudflare.com/ajax/libs/jspdf/2.5.1/jspdf.umd.min.js')); } Promise.all(libs).then(function() { var reader = new FileReader(); reader.onload = function(e) { var markdown = e.target.result || ''; var html = markdown; try { if (typeof marked !== 'undefined') html = marked.parse(markdown); } catch (err) { } var temp = document.createElement('div'); temp.innerHTML = html; var text = (temp.textContent || temp.innerText || '').replace(/\r\n?/g, '\n'); if (!text.trim()) text = ' '; var PDFCtor = (window.jspdf && window.jspdf.jsPDF) ? window.jspdf.jsPDF : window.jsPDF; if (!PDFCtor) { alert('PDF library failed to load.'); return; } var pdf = new PDFCtor({ orientation: 'p', unit: 'pt', format: 'a4' }); var margin = 40; var lineHeight = 16; var pageWidth = pdf.internal.pageSize.getWidth(); var pageHeight = pdf.internal.pageSize.getHeight(); var maxWidth = pageWidth - (margin * 2); var y = margin; pdf.setFont('times', 'normal'); pdf.setFontSize(12); var paragraphs = text.split('\n'); for (var i = 0; i < paragraphs.length; i++) { var para = paragraphs[i]; var lines = pdf.splitTextToSize(para.length ? para : ' ', maxWidth); for (var j = 0; j < lines.length; j++) { if (y > pageHeight - margin) { pdf.addPage(); y = margin; } pdf.text(lines[j], margin, y); y += lineHeight; } if (para.trim() === '') y += 6; } var baseName = fileName.replace(/\.[^.]+$/, ''); if (baseName === fileName) baseName += '-converted'; add_file_output(URL.createObjectURL(pdf.output('blob')), baseName + '.pdf'); }; reader.readAsText(blob); }).catch(function() { alert('Could not load markdown/PDF libraries.'); }); } var _loadedScripts = {}; function loadScriptPromise(url) { if (_loadedScripts[url]) return _loadedScripts[url]; _loadedScripts[url] = new Promise(function (resolve, reject) { var s = document.createElement('script'); s.src = url; s.onload = resolve; s.onerror = reject; document.head.appendChild(s); }); return _loadedScripts[url]; } function replaceAll(find, replace, str) { return str.replace(new RegExp(find, 'g'), replace); } function beautify(str) { var result = ''; var length = str.length; var i = 0; var braceCountLeft = 0; var braceCountRight = 0; var withinQuotes = false; while (i < length) { var c = str[i]; if (c == '"' && (i == 0 || c[i - 1] != '\\')) { // non-escaped quotes withinQuotes = !withinQuotes; } if (!withinQuotes && (c == '}' || c == '{' || c == ',')) { console.log('Start####' + result); // look back and remove carriage returns and whitespace that are already there var resultIndex = result.length - 1; while (resultIndex >= 0 && (result[resultIndex] == ' ' || result[resultIndex] == '\r' || result[resultIndex] == '\n' || result[resultIndex] == '\t')) { resultIndex = resultIndex - 1; result = result.substr(0, resultIndex + 1); console.log('char ' + result[resultIndex] + '-----' + result + 'zzz ' + result.length + ' ' + resultIndex); } if (c == '{') { braceCountLeft++; result += c + '\r' + GetTabs(braceCountLeft - braceCountRight); } else if (c == '}') { braceCountRight++; // precede with carriage return result += '\r' + GetTabs(braceCountLeft - braceCountRight) + c; } else if (c == ',') { result += c + '\r' + GetTabs(braceCountLeft - braceCountRight); } var nextChar = ''; // advance through whitespace and remove carriage returns that are already there while (i < length && (str[i + 1] == ' ' || str[i + 1] == '\r' || str[i + 1] == '\n' || str[i + 1] == '\t')) { i++; } } else { result += str[i]; } i++; } return result; } function GetTabs(count) { var result = ''; for (var i = 0; i < count; i++) { result += ' '; } return result; }